#!/usr/bin/env python3
# coding=utf-8

import numpy as np
import pandas as pd
import random as rd
import copy as cp
import plotly.express as px
import plotly.graph_objects as go

x = np.array(range(-50, 51, 1))
x2 = np.array(range(-2, 3, 1))
y = np.zeros(len(x), dtype=float)
y_noised = np.zeros(len(x), dtype=float)
kernel = np.zeros(len(x2), dtype=float)

# 原始序列
k = 0
for i in x:
    y[k] = i * i
    k = k + 1

# 原始序列加噪
for i in range(0, len(y)):
    y_noised[i] = y[i] + rd.uniform(-300, 300)

# 生成核
k = 0
for i in x2:
    kernel[k] = -i * i * i * i + 1000
    k = k + 1
# 直接指定核
kernela = np.array([1.0, 1.0, 1.0, 1.0, 1.0])
kernelb = np.array([1.0, 5.0, 10.0, 5.0, 1.0])
kernelc = np.array([10.0, 5.0, 1.0, 5.0, 10.0])
# 归一化后的核
nkernela = kernela / sum(kernela)
nkernelb = kernelb / sum(kernelb)
nkernelc = kernelc / sum(kernelc)
print(nkernela)
print(nkernelb)
print(nkernelc)

# 一维卷积
za = np.convolve(y_noised, nkernela, mode='same')
zb = np.convolve(y_noised, nkernelb, mode='same')
zc = np.convolve(y_noised, nkernelc, mode='same')

df = pd.DataFrame(data={
    'x': x,
    'src': y,
    'noised': y_noised,
    'za': za,
    'zb': zb,
    'zc': zc
})

part = df[8:len(df) - 8]

erra = np.mean(abs(part['noised'] - part['za']))
errb = np.mean(abs(part['noised'] - part['zb']))
errc = np.mean(abs(part['noised'] - part['zc']))

erras = np.mean(abs(part['src'] - part['za']))
errbs = np.mean(abs(part['src'] - part['zb']))
errcs = np.mean(abs(part['src'] - part['zc']))

print(erra, errb, errc)
print(erras, errbs, errcs)

fig = go.Figure()
# Add traces
fig.add_trace(go.Scatter(x=part['x'], y=part['src'],
                         line=dict(color='rgba(100,100,100,0.2)', width=25),
                         mode='lines',
                         name='原始'))
fig.add_trace(go.Scatter(x=part['x'], y=part['noised'],
                         line=dict(color='rgba(0,0,0,0.4)',
                                   width=5, dash='dot'),
                         mode='lines',
                         name='加噪后'))
fig.add_trace(go.Scatter(x=part['x'], y=part['za'],
                         line=dict(color='rgba(0,0,255,1)', width=7),
                         mode='lines',
                         name='卷积[1,1,1,1,1]'))
fig.add_trace(go.Scatter(x=part['x'], y=part['zb'],
                         line=dict(color='rgba(255,0,0,1)', width=7),
                         mode='lines',
                         name='卷积[1,5,10,5,1]'))
fig.add_trace(go.Scatter(x=part['x'], y=part['zc'],
                         line=dict(color='rgba(0,255,0,1)', width=7),
                         mode='lines',
                         name='卷积[10,5,1,5,10]'))
# Edit the layout
fig.update_layout(title='曲线一维卷积',
                  xaxis_title='x',
                  yaxis_title='取值')

fig.update_layout(title={
    'y': 0.87,
    'font': {
        'size': 38,
    }
})


fig.update_layout(legend={
    'orientation': 'v',
    'yanchor': "bottom",  # y轴顶部
    'y': 0.01,
    'xanchor': "right",
    'x': 0.99,
    'font': {
        'size': 25,
    },
    'title': {
        'text': '',
    }
})

fig.show()						# 展示图表
